package ParseWhere;
/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */



import java.util.*;
import java.util.regex.*;

import database.Row;
import database.*;
/**
 *
 * @author Dung Doan
 */
public class ExpressionNode extends Node
{
    private String m_attribute;
    private String m_table;
    private String m_operator;
    private Object m_value;
    
    /**
	 * @return the m_attribute
	 */
	public String getM_attribute() {
		return m_attribute;
	}
	/**
	 * @param m_attribute the m_attribute to set
	 */
	public void setM_attribute(String m_attribute) {
		this.m_attribute = m_attribute;
	}
	public ExpressionNode(String table, String attribute, String operator, Object value)
    {
        m_table = table;
        m_attribute = attribute;
        m_operator = operator;
        m_value = value;
        
    }
    public ExpressionNode(String attribute, String operator, Object value)
    {
        m_attribute = attribute;
        m_operator = operator;
        m_value = value;
        String REGEX = "\\.";
        Pattern p = Pattern.compile(REGEX);
        String[] items = p.split(m_attribute);
        if (items.length == 2)
        {
	        m_attribute = items[1];
	        m_table = items[0];
        }
        else
        {
        	m_attribute = attribute;
        	m_table = null;
        }
    }
    public ExpressionNode(String command)
    {
        
        String REGEX = new String();
        //System.out.println(command);
        if (command.indexOf("=") != -1)
            REGEX = m_operator = "=";
        if (command.indexOf(">") != -1)
            REGEX = m_operator = ">";
        if (command.indexOf("<") != -1)
            REGEX = m_operator = "<";
        if (command.indexOf(">=") != -1)
            REGEX = m_operator = ">=";
        if (command.indexOf("<=") != -1)
            REGEX = m_operator = "<=";
        if (command.indexOf("!=") != -1)
            REGEX = m_operator = "!=";
        
        Pattern p = Pattern.compile(REGEX);
        String[] items = p.split(command);
        for (int i = 0 ; i < items.length ; i++)
            items[i] = Normalize(items[i]);
        
        
        m_attribute = items[0];
        m_value = items[1];
        m_table = null;
//        System.out.println(m_attribute);
//        System.out.println(m_operator);
//        System.out.println(m_value);
//        REGEX = "\\.";
//        p = Pattern.compile(REGEX);
//        
//        items = p.split(m_attribute);
//        for (int i = 0 ; i < items.length ; i++)
//            items[i] = Normalize(items[i]);
//        m_table = items[0];
//        m_attribute = items[1];
    }
    public static String Normalize(String str)
    {
        String result = new String(str);
        int i;
        for (i = 0 ; i < result.length() ; i++)
            if (result.charAt(i) != ' ')
                break;
        
        result = result.substring(i);
        for (i = result.length() - 1 ; i >= 0 ; i--)
            if (result.charAt(i) != ' ')
                break;
        result = result.substring(0, i + 1);
        boolean flag = true;
        for (i = 0 ; i < result.length(); i++)
            if (result.charAt(i) != ' ')
            {
                flag = false;
                break;
            }
        if (flag == true)
            result = null;
        return result;
    }
    @Override
    public String getNodeType() {
        return "expression";
    }
    @Override
    public boolean check(List<Field> columnName, Row data)
    {
        int index = FindColumnName(columnName, m_attribute);
        if (index < 0)
            return false;
        int index2 = FindColumnName(columnName, m_value.toString());
        if (index2 < 0)
        {
            List<Object> cell_list = data.get_data();
            //System.out.println(cell_list.get(index).getM_obj());
            //if (cell_list.get(index).getClass() == String.class)
            if (columnName.get(index).get_dataType().equalsIgnoreCase("string") == true)
            {
                String value = m_value.toString();
                value = value.substring(1, value.length() - 1);
                if (value.equals(cell_list.get(index).toString()))
                    return true;
                return false;
            }
            //int value = (int) m_value;
            int value = String2Int((String)m_value);        
            int value_query = String2Int((String)cell_list.get(index));
            if (m_operator.equals("="))
                if (value == value_query)
                    return true;
            if (m_operator.equals(">"))
                if (value > value_query)
                    return true;
            if (m_operator.equals("<"))
                if (value < value_query)
                    return true;
            if (m_operator.equals(">="))
                if (value >= value_query)
                    return true;
            if (m_operator.equals("<="))
                if (value <= value_query)
                    return true;

            return false;
        }
        else
        {
            List<Object> cell_list = data.get_data();
            //if (cell_list.get(index).getClass() == cell_list.get(index2).getClass())
            if (columnName.get(index).get_dataType().equalsIgnoreCase(columnName.get(index2).get_dataType()))
            {
                //if (cell_list.get(index).getClass() == String.class)
                if (columnName.get(index).get_dataType().equalsIgnoreCase("string") == true)
            	{
                    String str1 = cell_list.get(index).toString();
                    String str2 = cell_list.get(index2).toString();
                    if (str1.equals(str2))
                        return true;
                    return false;
                    
                }
                int num1 = (Integer)cell_list.get(index);
                int num2 = (Integer)cell_list.get(index2);
                if (num1 == num2)
                    return true;
                return false;
                    
            }
            
        }
        return false;
        
        
    }
    private int String2Int(String str)
    {
        int num = 0;
        for (int i = 0 ; i < str.length() ; i++)
        {
            num = num * 10;
            num = num + (str.charAt(i) - '0');
        }
        return num;
    }
    public int FindColumnName(List<Field> columnName, String column)
    {
        
        for (int i = 0 ; i < columnName.size() ; i++)
            if (columnName.get(i).get_name().equalsIgnoreCase(column) == true)
                return i;
        return -1;
        
        //org.gibello.zql.zql
    }

    @Override
    public void Display() 
    {
        System.out.println(m_table + "." + m_attribute + m_operator + m_value);
    }

    @Override
    public void AddSubNode(Node node) {
        //throw new UnsupportedOperationException("Not supported yet.");
        return;
    }
	/**
	 * @return the m_value
	 */
	public Object getM_value() {
		return m_value;
	}
	/**
	 * @param m_value the m_value to set
	 */
	public void setM_value(Object m_value) {
		this.m_value = m_value;
	}
}
